package ru.surfstudio.webservicetemplate.service;

import java.io.Serializable;
import java.net.URI;

import org.springframework.http.client.ClientHttpRequestFactory;
import org.springframework.util.Assert;
import org.springframework.web.client.RestClientException;
import org.springframework.web.client.RestTemplate;
import org.springframework.web.util.UriTemplate;

import ru.surfstudio.webservicetemplate.exception.AuthenticationException;
import ru.surfstudio.webservicetemplate.exception.TransportException;
import ru.surfstudio.webservicetemplate.parser.Parser;
import ru.surfstudio.webservicetemplate.task.GetHttpTask;

public class RestExecutor {
	
	/** Root URL of web-service */
    private static final String URL = "";
    
    /** Count of attempts */
    private static final int RETRY = 2;
	
	private ClientHttpRequestFactory clientHttpRequestFactory;

	public RestExecutor(ClientHttpRequestFactory clientHttpRequestFactory) {
		this.clientHttpRequestFactory = clientHttpRequestFactory;
	}

	public Serializable getForObject(GetHttpTask httpTask) throws AuthenticationException, TransportException {
		Assert.notNull(httpTask, "httpTask must not be null");
		RestTemplate restTemplate = new RestTemplate(clientHttpRequestFactory);
		String requestUrl = URL + httpTask.getMethodName();
		UriTemplate template = new UriTemplate(requestUrl);
		URI uri = template.expand(httpTask.getParams());
		int count = 0;
        while (count < RETRY) {
            count++;
            try {
                String response = restTemplate.getForObject(uri, String.class);
                Parser<?> parser = httpTask.getParser();
                return (parser != null) ? parser.parse(response) : null;
            } catch (RestClientException e) {
                if (count >= RETRY) {
                    throw e;
                }
            }
        }
        throw new RestClientException("Request problem");
	}
}